package parser

import (
	"encoding/json"
	"fmt"
	"reflect"
)

// JSONSerializer 提供AST节点的JSON序列化功能
type JSONSerializer struct {
	Indent bool // 是否使用缩进格式化
}

// NewJSONSerializer 创建新的JSON序列化器
func NewJSONSerializer(indent bool) *JSONSerializer {
	return &JSONSerializer{Indent: indent}
}

// Serialize 将AST节点序列化为JSON字符串
func (js *JSONSerializer) Serialize(node Node) (string, error) {
	if node == nil {
		return "null", nil
	}
	
	data := js.nodeToMap(node)
	
	var result []byte
	var err error
	
	if js.Indent {
		result, err = json.MarshalIndent(data, "", "  ")
	} else {
		result, err = json.Marshal(data)
	}
	
	if err != nil {
		return "", fmt.Errorf("failed to serialize AST node: %w", err)
	}
	
	return string(result), nil
}

// SerializeToBytes 将AST节点序列化为JSON字节数组
func (js *JSONSerializer) SerializeToBytes(node Node) ([]byte, error) {
	if node == nil {
		return []byte("null"), nil
	}
	
	data := js.nodeToMap(node)
	
	var result []byte
	var err error
	
	if js.Indent {
		result, err = json.MarshalIndent(data, "", "  ")
	} else {
		result, err = json.Marshal(data)
	}
	
	if err != nil {
		return nil, fmt.Errorf("failed to serialize AST node: %w", err)
	}
	
	return result, nil
}

// nodeToMap 将AST节点转换为map[string]interface{}
func (js *JSONSerializer) nodeToMap(node Node) map[string]interface{} {
	if node == nil {
		return nil
	}
	
	result := make(map[string]interface{})
	result["type"] = js.getNodeType(node)
	
	switch n := node.(type) {
	case *SelectStmt:
		js.serializeSelectStmt(result, n)
	case *InsertStmt:
		js.serializeInsertStmt(result, n)
	case *UpdateStmt:
		js.serializeUpdateStmt(result, n)
	case *DeleteStmt:
		js.serializeDeleteStmt(result, n)
	case *CreateTableStmt:
		js.serializeCreateTableStmt(result, n)
	case *AlterTableStmt:
		js.serializeAlterTableStmt(result, n)
	case *DropTableStmt:
		js.serializeDropTableStmt(result, n)
	case *CreateIndexStmt:
		js.serializeCreateIndexStmt(result, n)
	case *DropIndexStmt:
		js.serializeDropIndexStmt(result, n)
	case *CreateViewStmt:
		js.serializeCreateViewStmt(result, n)
	case *DropViewStmt:
		js.serializeDropViewStmt(result, n)
	case *GrantStmt:
		js.serializeGrantStmt(result, n)
	case *RevokeStmt:
		js.serializeRevokeStmt(result, n)
	case *BeginStmt:
		js.serializeBeginStmt(result, n)
	case *CommitStmt:
		js.serializeCommitStmt(result, n)
	case *RollbackStmt:
		js.serializeRollbackStmt(result, n)
	case *SavepointStmt:
		js.serializeSavepointStmt(result, n)
	case *ReleaseSavepointStmt:
		js.serializeReleaseSavepointStmt(result, n)
	case *ColumnRef:
		js.serializeColumnRef(result, n)
	case *Literal:
		js.serializeLiteral(result, n)
	case *BinaryExpr:
		js.serializeBinaryExpr(result, n)
	case *UnaryExpr:
		js.serializeUnaryExpr(result, n)
	case *FunctionCall:
		js.serializeFunctionCall(result, n)
	case *SubqueryExpr:
		js.serializeSubqueryExpr(result, n)
	case *CaseExpr:
		js.serializeCaseExpr(result, n)
	case *ArrayExpr:
		js.serializeArrayExpr(result, n)
	case *ArrayAccess:
		js.serializeArrayAccess(result, n)
	case *JSONBExpr:
		js.serializeJSONBExpr(result, n)
	case *TableRef:
		js.serializeTableRef(result, n)
	case *JoinExpr:
		js.serializeJoinExpr(result, n)
	case *OrderByExpr:
		js.serializeOrderByExpr(result, n)
	case *UpdateExpr:
		js.serializeUpdateExpr(result, n)
	case *WithClause:
		js.serializeWithClause(result, n)
	case *CommonTableExpr:
		js.serializeCommonTableExpr(result, n)
	default:
		// 使用反射处理未知类型
		js.serializeGeneric(result, node)
	}
	
	return result
}

// getNodeType 获取节点类型名称
func (js *JSONSerializer) getNodeType(node Node) string {
	t := reflect.TypeOf(node)
	if t.Kind() == reflect.Ptr {
		t = t.Elem()
	}
	return t.Name()
}

// 序列化具体节点类型的方法

func (js *JSONSerializer) serializeSelectStmt(result map[string]interface{}, stmt *SelectStmt) {
	result["distinct"] = stmt.Distinct
	
	if len(stmt.Targets) > 0 {
		targets := make([]interface{}, len(stmt.Targets))
		for i, target := range stmt.Targets {
			targets[i] = js.nodeToMap(target)
		}
		result["targets"] = targets
	}
	
	if len(stmt.From) > 0 {
		from := make([]interface{}, len(stmt.From))
		for i, f := range stmt.From {
			from[i] = js.nodeToMap(&f)
		}
		result["from"] = from
	}
	
	if stmt.Where != nil {
		result["where"] = js.nodeToMap(stmt.Where)
	}
	
	if len(stmt.GroupBy) > 0 {
		groupBy := make([]interface{}, len(stmt.GroupBy))
		for i, gb := range stmt.GroupBy {
			groupBy[i] = js.nodeToMap(gb)
		}
		result["groupBy"] = groupBy
	}
	
	if stmt.Having != nil {
		result["having"] = js.nodeToMap(stmt.Having)
	}
	
	if len(stmt.OrderBy) > 0 {
		orderBy := make([]interface{}, len(stmt.OrderBy))
		for i, ob := range stmt.OrderBy {
			orderBy[i] = js.nodeToMap(&ob)
		}
		result["orderBy"] = orderBy
	}
	
	if stmt.Limit != nil {
		result["limit"] = js.nodeToMap(stmt.Limit)
	}
	
	if stmt.Offset != nil {
		result["offset"] = js.nodeToMap(stmt.Offset)
	}
}

func (js *JSONSerializer) serializeInsertStmt(result map[string]interface{}, stmt *InsertStmt) {
	if stmt.Table != nil {
		result["table"] = js.nodeToMap(stmt.Table)
	}
	
	if len(stmt.Columns) > 0 {
		result["columns"] = stmt.Columns
	}
	
	if len(stmt.Values) > 0 {
		values := make([]interface{}, len(stmt.Values))
		for i, row := range stmt.Values {
			rowValues := make([]interface{}, len(row))
			for j, val := range row {
				rowValues[j] = js.nodeToMap(val)
			}
			values[i] = rowValues
		}
		result["values"] = values
	}
	
	if stmt.Select != nil {
		result["select"] = js.nodeToMap(stmt.Select)
	}
}

func (js *JSONSerializer) serializeUpdateStmt(result map[string]interface{}, stmt *UpdateStmt) {
	if stmt.Table != nil {
		result["table"] = js.nodeToMap(stmt.Table)
	}
	
	if len(stmt.Set) > 0 {
		set := make([]interface{}, len(stmt.Set))
		for i, s := range stmt.Set {
			set[i] = js.nodeToMap(&s)
		}
		result["set"] = set
	}
	
	if stmt.Where != nil {
		result["where"] = js.nodeToMap(stmt.Where)
	}
}

func (js *JSONSerializer) serializeDeleteStmt(result map[string]interface{}, stmt *DeleteStmt) {
	if stmt.Table != nil {
		result["table"] = js.nodeToMap(stmt.Table)
	}
	
	if stmt.Where != nil {
		result["where"] = js.nodeToMap(stmt.Where)
	}
}

func (js *JSONSerializer) serializeCreateTableStmt(result map[string]interface{}, stmt *CreateTableStmt) {
	if stmt.Table != nil {
		result["table"] = js.nodeToMap(stmt.Table)
	}
	result["ifNotExists"] = stmt.IfNotExists
	result["temporary"] = stmt.Temporary
	result["unlogged"] = stmt.Unlogged
	
	if len(stmt.Columns) > 0 {
		columns := make([]interface{}, len(stmt.Columns))
		for i, col := range stmt.Columns {
			colData := map[string]interface{}{
				"name": col.Name,
			}
			if col.Type != nil {
				colData["type"] = map[string]interface{}{
					"name":      col.Type.Name,
					"size":      col.Type.Size,
					"arrayDims": col.Type.ArrayDims,
					"timezone":  col.Type.Timezone,
				}
			}
			if col.Default != nil {
				colData["default"] = js.nodeToMap(col.Default)
			}
			if len(col.Constraints) > 0 {
				constraints := make([]interface{}, len(col.Constraints))
				for j, constraint := range col.Constraints {
					constraints[j] = map[string]interface{}{
						"name": constraint.Name,
						"type": constraint.Type,
					}
				}
				colData["constraints"] = constraints
			}
			columns[i] = colData
		}
		result["columns"] = columns
	}
	
	if len(stmt.Constraints) > 0 {
		constraints := make([]interface{}, len(stmt.Constraints))
		for i, constraint := range stmt.Constraints {
			constraintData := map[string]interface{}{
				"type": constraint.Type,
				"name": constraint.Name,
			}
			if len(constraint.Columns) > 0 {
				constraintData["columns"] = constraint.Columns
			}
			if constraint.References != nil {
				constraintData["references"] = map[string]interface{}{
					"table":    js.nodeToMap(constraint.References.Table),
					"columns":  constraint.References.Columns,
					"onDelete": constraint.References.OnDelete,
					"onUpdate": constraint.References.OnUpdate,
					"match":    constraint.References.Match,
				}
			}
			constraints[i] = constraintData
		}
		result["constraints"] = constraints
	}
	
	if len(stmt.Inherits) > 0 {
		inherits := make([]interface{}, len(stmt.Inherits))
		for i, inherit := range stmt.Inherits {
			inherits[i] = js.nodeToMap(inherit)
		}
		result["inherits"] = inherits
	}
}

func (js *JSONSerializer) serializeAlterTableStmt(result map[string]interface{}, stmt *AlterTableStmt) {
	if stmt.Table != nil {
		result["table"] = js.nodeToMap(stmt.Table)
	}
	
	if len(stmt.Actions) > 0 {
		actions := make([]interface{}, len(stmt.Actions))
		for i, action := range stmt.Actions {
			actionData := map[string]interface{}{
				"type": action.Type,
			}
			if action.Column != nil {
				actionData["column"] = map[string]interface{}{
					"name": action.Column.Name,
				}
				if action.Column.Type != nil {
					actionData["columnType"] = map[string]interface{}{
						"name":      action.Column.Type.Name,
						"size":      action.Column.Type.Size,
						"arrayDims": action.Column.Type.ArrayDims,
						"timezone":  action.Column.Type.Timezone,
					}
				}
			}
			if action.Constraint != nil {
				actionData["constraint"] = map[string]interface{}{
					"name": action.Constraint.Name,
					"type": action.Constraint.Type,
				}
			}
			if action.OldName != "" {
				actionData["oldName"] = action.OldName
			}
			if action.NewName != "" {
				actionData["newName"] = action.NewName
			}
			actionData["ifExists"] = action.IfExists
			actions[i] = actionData
		}
		result["actions"] = actions
	}
}

func (js *JSONSerializer) serializeDropTableStmt(result map[string]interface{}, stmt *DropTableStmt) {
	if len(stmt.Tables) > 0 {
		tables := make([]interface{}, len(stmt.Tables))
		for i, table := range stmt.Tables {
			tables[i] = js.nodeToMap(table)
		}
		result["tables"] = tables
	}
	result["ifExists"] = stmt.IfExists
	result["cascade"] = stmt.Cascade
}

func (js *JSONSerializer) serializeCreateIndexStmt(result map[string]interface{}, stmt *CreateIndexStmt) {
	result["name"] = stmt.Name
	if stmt.Table != nil {
		result["table"] = js.nodeToMap(stmt.Table)
	}
	if len(stmt.Columns) > 0 {
		columns := make([]interface{}, len(stmt.Columns))
		for i, col := range stmt.Columns {
			columns[i] = map[string]interface{}{
				"expr":      js.nodeToMap(col.Expr),
				"direction": col.Direction,
				"nulls":     col.Nulls,
				"opClass":   col.OpClass,
			}
		}
		result["columns"] = columns
	}
	result["unique"] = stmt.Unique
	result["concurrent"] = stmt.Concurrent
	result["ifNotExists"] = stmt.IfNotExists
	result["method"] = stmt.Method
	result["tablespace"] = stmt.Tablespace
	
	if stmt.Where != nil {
		result["where"] = js.nodeToMap(stmt.Where)
	}
}

func (js *JSONSerializer) serializeDropIndexStmt(result map[string]interface{}, stmt *DropIndexStmt) {
	result["indexes"] = stmt.Indexes
	result["ifExists"] = stmt.IfExists
	result["cascade"] = stmt.Cascade
	result["concurrent"] = stmt.Concurrent
}

func (js *JSONSerializer) serializeCreateViewStmt(result map[string]interface{}, stmt *CreateViewStmt) {
	if stmt.Name != nil {
		result["name"] = js.nodeToMap(stmt.Name)
	}
	result["replace"] = stmt.Replace
	result["temporary"] = stmt.Temporary
	result["recursive"] = stmt.Recursive
	result["checkOption"] = stmt.CheckOption
	result["security"] = stmt.Security
	
	if len(stmt.Columns) > 0 {
		result["columns"] = stmt.Columns
	}
	
	if stmt.Select != nil {
		result["select"] = js.nodeToMap(stmt.Select)
	}
}

func (js *JSONSerializer) serializeDropViewStmt(result map[string]interface{}, stmt *DropViewStmt) {
	if len(stmt.Views) > 0 {
		views := make([]interface{}, len(stmt.Views))
		for i, view := range stmt.Views {
			views[i] = js.nodeToMap(view)
		}
		result["views"] = views
	}
	result["ifExists"] = stmt.IfExists
	result["cascade"] = stmt.Cascade
}

func (js *JSONSerializer) serializeGrantStmt(result map[string]interface{}, stmt *GrantStmt) {
	if len(stmt.Privileges) > 0 {
		privileges := make([]interface{}, len(stmt.Privileges))
		for i, priv := range stmt.Privileges {
			privileges[i] = map[string]interface{}{
				"type":    priv.Type,
				"columns": priv.Columns,
			}
		}
		result["privileges"] = privileges
	}
	if len(stmt.Objects) > 0 {
		objects := make([]interface{}, len(stmt.Objects))
		for i, obj := range stmt.Objects {
			objects[i] = map[string]interface{}{
				"type": obj.Type,
				"name": obj.Name,
			}
		}
		result["objects"] = objects
	}
	result["grantees"] = stmt.Grantees
	result["withGrant"] = stmt.WithGrant
	result["grantedBy"] = stmt.GrantedBy
}

func (js *JSONSerializer) serializeRevokeStmt(result map[string]interface{}, stmt *RevokeStmt) {
	if len(stmt.Privileges) > 0 {
		privileges := make([]interface{}, len(stmt.Privileges))
		for i, priv := range stmt.Privileges {
			privileges[i] = map[string]interface{}{
				"type":    priv.Type,
				"columns": priv.Columns,
			}
		}
		result["privileges"] = privileges
	}
	if len(stmt.Objects) > 0 {
		objects := make([]interface{}, len(stmt.Objects))
		for i, obj := range stmt.Objects {
			objects[i] = map[string]interface{}{
				"type": obj.Type,
				"name": obj.Name,
			}
		}
		result["objects"] = objects
	}
	result["grantees"] = stmt.Grantees
	result["cascade"] = stmt.Cascade
	result["grantOption"] = stmt.GrantOption
	result["grantedBy"] = stmt.GrantedBy
}

func (js *JSONSerializer) serializeBeginStmt(result map[string]interface{}, stmt *BeginStmt) {
	result["isolationLevel"] = stmt.IsolationLevel
	if stmt.ReadOnly != nil {
		result["readOnly"] = *stmt.ReadOnly
	}
	if stmt.Deferrable != nil {
		result["deferrable"] = *stmt.Deferrable
	}
}

func (js *JSONSerializer) serializeCommitStmt(result map[string]interface{}, stmt *CommitStmt) {
	result["chain"] = stmt.Chain
}

func (js *JSONSerializer) serializeRollbackStmt(result map[string]interface{}, stmt *RollbackStmt) {
	result["chain"] = stmt.Chain
	if stmt.Savepoint != "" {
		result["savepoint"] = stmt.Savepoint
	}
}

func (js *JSONSerializer) serializeSavepointStmt(result map[string]interface{}, stmt *SavepointStmt) {
	result["name"] = stmt.Name
}

func (js *JSONSerializer) serializeReleaseSavepointStmt(result map[string]interface{}, stmt *ReleaseSavepointStmt) {
	result["name"] = stmt.Name
}

func (js *JSONSerializer) serializeColumnRef(result map[string]interface{}, expr *ColumnRef) {
	result["column"] = expr.Column
	if expr.Table != "" {
		result["table"] = expr.Table
	}
}

func (js *JSONSerializer) serializeLiteral(result map[string]interface{}, expr *Literal) {
	result["value"] = expr.Value
	result["dataType"] = expr.Type
}

func (js *JSONSerializer) serializeBinaryExpr(result map[string]interface{}, expr *BinaryExpr) {
	result["operator"] = expr.Operator
	result["left"] = js.nodeToMap(expr.Left)
	result["right"] = js.nodeToMap(expr.Right)
}

func (js *JSONSerializer) serializeUnaryExpr(result map[string]interface{}, expr *UnaryExpr) {
	result["operator"] = expr.Operator
	result["operand"] = js.nodeToMap(expr.Operand)
}

func (js *JSONSerializer) serializeFunctionCall(result map[string]interface{}, expr *FunctionCall) {
	result["name"] = expr.Name
	result["distinct"] = expr.Distinct
	
	if len(expr.Args) > 0 {
		args := make([]interface{}, len(expr.Args))
		for i, arg := range expr.Args {
			args[i] = js.nodeToMap(arg)
		}
		result["args"] = args
	}
	
	if expr.Over != nil {
		over := make(map[string]interface{})
		js.serializeWindowSpec(over, expr.Over)
		result["over"] = over
	}
}

func (js *JSONSerializer) serializeSubqueryExpr(result map[string]interface{}, expr *SubqueryExpr) {
	if expr.Select != nil {
		result["select"] = js.nodeToMap(expr.Select)
	}
}

func (js *JSONSerializer) serializeCaseExpr(result map[string]interface{}, expr *CaseExpr) {
	if expr.Expr != nil {
		result["expr"] = js.nodeToMap(expr.Expr)
	}
	
	if len(expr.WhenList) > 0 {
		whenList := make([]interface{}, len(expr.WhenList))
		for i, when := range expr.WhenList {
			whenData := map[string]interface{}{
				"condition": js.nodeToMap(when.Condition),
				"result":    js.nodeToMap(when.Result),
			}
			whenList[i] = whenData
		}
		result["whenList"] = whenList
	}
	
	if expr.Else != nil {
		result["else"] = js.nodeToMap(expr.Else)
	}
}

func (js *JSONSerializer) serializeArrayExpr(result map[string]interface{}, expr *ArrayExpr) {
	if len(expr.Elements) > 0 {
		elements := make([]interface{}, len(expr.Elements))
		for i, element := range expr.Elements {
			elements[i] = js.nodeToMap(element)
		}
		result["elements"] = elements
	}
}

func (js *JSONSerializer) serializeArrayAccess(result map[string]interface{}, expr *ArrayAccess) {
	result["array"] = js.nodeToMap(expr.Array)
	result["index"] = js.nodeToMap(expr.Index)
}

func (js *JSONSerializer) serializeJSONBExpr(result map[string]interface{}, expr *JSONBExpr) {
	result["operator"] = expr.Operator
	result["left"] = js.nodeToMap(expr.Left)
	result["right"] = js.nodeToMap(expr.Right)
}

func (js *JSONSerializer) serializeTableRef(result map[string]interface{}, ref *TableRef) {
	result["name"] = ref.Name
	if ref.Alias != "" {
		result["alias"] = ref.Alias
	}
	
	if len(ref.Joins) > 0 {
		joins := make([]interface{}, len(ref.Joins))
		for i, join := range ref.Joins {
			joins[i] = js.nodeToMap(&join)
		}
		result["joins"] = joins
	}
}

func (js *JSONSerializer) serializeJoinExpr(result map[string]interface{}, expr *JoinExpr) {
	result["type"] = expr.Type
	result["table"] = js.nodeToMap(expr.Table)
	
	if expr.Condition != nil {
		result["condition"] = js.nodeToMap(expr.Condition)
	}
}

func (js *JSONSerializer) serializeOrderByExpr(result map[string]interface{}, expr *OrderByExpr) {
	result["expr"] = js.nodeToMap(expr.Expr)
	result["direction"] = expr.Direction
	result["nulls"] = expr.Nulls
}

func (js *JSONSerializer) serializeUpdateExpr(result map[string]interface{}, expr *UpdateExpr) {
	result["column"] = expr.Column
	result["value"] = js.nodeToMap(expr.Value)
}

func (js *JSONSerializer) serializeWithClause(result map[string]interface{}, clause *WithClause) {
	result["recursive"] = clause.Recursive
	
	if len(clause.CTEs) > 0 {
		ctes := make([]interface{}, len(clause.CTEs))
		for i, cte := range clause.CTEs {
			ctes[i] = js.nodeToMap(cte)
		}
		result["ctes"] = ctes
	}
}

func (js *JSONSerializer) serializeCommonTableExpr(result map[string]interface{}, expr *CommonTableExpr) {
	result["name"] = expr.Name
	
	if len(expr.Columns) > 0 {
		result["columns"] = expr.Columns
	}
	
	if expr.Query != nil {
		result["query"] = js.nodeToMap(expr.Query)
	}
	
	if expr.Search != nil {
		searchData := map[string]interface{}{
			"type":    expr.Search.Type,
			"columns": expr.Search.Columns,
			"setName": expr.Search.SetName,
		}
		result["search"] = searchData
	}
	
	if expr.Cycle != nil {
		cycleData := map[string]interface{}{
			"columns":      expr.Cycle.Columns,
			"setName":      expr.Cycle.SetName,
			"using":        expr.Cycle.Using,
			"cycleValue":   js.nodeToMap(expr.Cycle.CycleValue),
			"defaultValue": js.nodeToMap(expr.Cycle.DefaultValue),
		}
		result["cycle"] = cycleData
	}
}

func (js *JSONSerializer) serializeWindowSpec(result map[string]interface{}, spec *WindowSpec) {
	if len(spec.PartitionBy) > 0 {
		partitionBy := make([]interface{}, len(spec.PartitionBy))
		for i, expr := range spec.PartitionBy {
			partitionBy[i] = js.nodeToMap(expr)
		}
		result["partitionBy"] = partitionBy
	}
	
	if len(spec.OrderBy) > 0 {
		orderBy := make([]interface{}, len(spec.OrderBy))
		for i, ob := range spec.OrderBy {
			orderBy[i] = js.nodeToMap(&ob)
		}
		result["orderBy"] = orderBy
	}
	
	if spec.Frame != nil {
		frame := make(map[string]interface{})
		js.serializeWindowFrame(frame, spec.Frame)
		result["frame"] = frame
	}
}

func (js *JSONSerializer) serializeWindowFrame(result map[string]interface{}, frame *WindowFrame) {
	result["type"] = frame.Type
	
	if frame.Start != nil {
		start := make(map[string]interface{})
		js.serializeFrameBound(start, frame.Start)
		result["start"] = start
	}
	
	if frame.End != nil {
		end := make(map[string]interface{})
		js.serializeFrameBound(end, frame.End)
		result["end"] = end
	}
}

func (js *JSONSerializer) serializeFrameBound(result map[string]interface{}, bound *FrameBound) {
	result["type"] = bound.Type
	
	if bound.Offset != nil {
		result["offset"] = js.nodeToMap(bound.Offset)
	}
}

// serializeGeneric 使用反射序列化未知类型
func (js *JSONSerializer) serializeGeneric(result map[string]interface{}, node Node) {
	v := reflect.ValueOf(node)
	if v.Kind() == reflect.Ptr {
		v = v.Elem()
	}
	
	if v.Kind() != reflect.Struct {
		return
	}
	
	t := v.Type()
	for i := 0; i < v.NumField(); i++ {
		field := v.Field(i)
		fieldType := t.Field(i)
		
		// 跳过未导出的字段
		if !field.CanInterface() {
			continue
		}
		
		fieldName := fieldType.Name
		// 转换为小写开头的JSON字段名
		if len(fieldName) > 0 {
			fieldName = string(fieldName[0]+32) + fieldName[1:] // 简单的大写转小写
		}
		
		result[fieldName] = field.Interface()
	}
}

// 便利函数

// ToJSON 将AST节点序列化为格式化的JSON字符串
func ToJSON(node Node) (string, error) {
	serializer := NewJSONSerializer(true)
	return serializer.Serialize(node)
}

// ToJSONCompact 将AST节点序列化为紧凑的JSON字符串
func ToJSONCompact(node Node) (string, error) {
	serializer := NewJSONSerializer(false)
	return serializer.Serialize(node)
}

// ToJSONBytes 将AST节点序列化为JSON字节数组
func ToJSONBytes(node Node) ([]byte, error) {
	serializer := NewJSONSerializer(true)
	return serializer.SerializeToBytes(node)
}

// ToJSONBytesCompact 将AST节点序列化为紧凑的JSON字节数组
func ToJSONBytesCompact(node Node) ([]byte, error) {
	serializer := NewJSONSerializer(false)
	return serializer.SerializeToBytes(node)
}